//
// Created by htlin on 2021/2/22 0022.
//

#include "Timer.h"

class TimerPrivateData {
public:
    uv_loop_t *loop;
    uv_timer_t *timer;
    Timer::OnTimer onTimer;
    void *userData;
    uint64_t timeout;
    uint64_t repeat;
};

Timer::Timer(uv_loop_t *loop) {
  data = std::make_unique<TimerPrivateData>();
  data->loop = loop;
  data->timer = static_cast<uv_timer_t *>(malloc(sizeof(uv_timer_t)));
  uv_timer_init(loop, data->timer);
}

Timer::~Timer() {
  free(data->timer);
}

void Timer::timerCB(uv_timer_t *handle) {
  auto *thisPointer = static_cast<Timer *>(handle->data);
  if (thisPointer->data->onTimer != nullptr) {
    thisPointer->data->onTimer(thisPointer->data->userData);
  }
}

void Timer::start(uint64_t timeout, uint64_t repeat) {
  data->timer->data = (void *) this;
  data->timeout = timeout;
  data->repeat = repeat;
  uv_timer_start(data->timer, Timer::timerCB, timeout, repeat);
}

void Timer::setTimerCallback(OnTimer onTimer, void *userData) {
  data->onTimer = onTimer;
  data->userData = userData;
}

void Timer::stop() {
  uv_timer_stop(data->timer);
}
